package com.qlh.camera.rgb

import com.qlh.camera.cnn.util.ImageSize
import org.opencv.core.*
import org.opencv.imgcodecs.Imgcodecs
import org.opencv.imgproc.Imgproc
import java.io.File
import java.io.FileWriter
import java.util.ArrayList
import kotlin.math.abs

object ImageUtil {

    /**
     * 获取RGB均值和方差
     */
    fun getRGBMeanStdDev(source: Mat): RgbMeanStdDev {
        val rgb = Mat()
        val rgbMeanStdDev = RgbMeanStdDev()
        Imgproc.cvtColor(source, rgb, Imgproc.COLOR_BGR2RGB) //转换颜色顺序BGR->RGB
        val mean = MatOfDouble() //r g b 均值数组
        val sigma = MatOfDouble() //r g b 方差数组
        //mask 当mask中对应位置的像素值不等于零的时候，src中相同位置的像素点才参与计算均值与标准方差
        val channels: List<Mat> = ArrayList() //arrayListOf<Mat>()
        Core.split(rgb, channels) //分离出RGB个通道
        Core.meanStdDev(rgb, mean, sigma, channels[0]) //计算均值和方差
        rgb.release()
        //封装数据返回
        if (mean.rows() == sigma.rows() && mean.cols() == sigma.cols()) { //结构一致
            rgbMeanStdDev.r = MeanStdDevBO(DoubleUtil.formatDouble(mean.toList()[0], DoubleUtil.Retain_Two),
                    DoubleUtil.formatDouble(sigma.toList()[0], DoubleUtil.Retain_Two))
            rgbMeanStdDev.g = MeanStdDevBO(DoubleUtil.formatDouble(mean.toList()[1], DoubleUtil.Retain_Two),
                    DoubleUtil.formatDouble(sigma.toList()[1], DoubleUtil.Retain_Two))
            rgbMeanStdDev.b = MeanStdDevBO(DoubleUtil.formatDouble(mean.toList()[2], DoubleUtil.Retain_Two),
                    DoubleUtil.formatDouble(sigma.toList()[2], DoubleUtil.Retain_Two))
        }
        return rgbMeanStdDev
    }

    fun saveData(data: String) {
        val file = File("F:\\Private_Project\\kmgCamera\\res\\data", "mt2.txt")
        val resultWf = FileWriter(file, true)
        try {
            resultWf.write(data)
            resultWf.write("\r\n")
            resultWf.flush()
        } catch (e: Exception) {
            e.printStackTrace()
        } finally {
            resultWf.close()
        }
    }

    //获取图片关键部分以及成熟度
    fun getKeyAreaMt(filePath: String): MTBO {
        val src = Imgcodecs.imread(filePath, Imgcodecs.IMREAD_UNCHANGED)
        Imgproc.resize(src, src, Size(3648.0, 1680.0))
        val w = src.cols()
        val h = src.rows()
        val keyRect = Rect(
                (ImageSize.xScale * w).toInt(),
                (ImageSize.yScale * h).toInt(),
                (w - 2 * ImageSize.xScale * w).toInt(),
                (h - 2 * ImageSize.yScale * h).toInt())
        val roiMat = Mat(src, keyRect)

        //获取样本成熟度系数
        val mt = ThresholdUtil.getMT(roiMat)
        //计算差值
        Standard.standardMt.forEach {
            it.diff = abs(mt - it.baseMt)
        }
        //排序
        val target = Standard.standardMt.sortedBy { it.diff }.first()
        src.release()
        roiMat.release()
        return target
    }

}